"""Session management service."""
from typing import Dict, Optional
from datetime import datetime
from app import db
from app.models.location import Location
from app.models.route import Route
from app.models.walking_session import WalkingSession


class SessionService:
    """Service for managing walking sessions."""
    
    def create_session(
        self,
        user_id: str,
        target_poi_id: str,
        route: Route
    ) -> WalkingSession:
        """Create a new walking session.
        
        Args:
            user_id: User ID
            target_poi_id: Target POI ID
            route: Route to follow
            
        Returns:
            Created session
        """
        import uuid
        
        # Create new session
        session = WalkingSession(
            id=str(uuid.uuid4()),
            user_id=user_id,
            route_id=route.id,
            status='active',
            start_time=datetime.utcnow(),
            current_latitude=route.start_latitude,
            current_longitude=route.start_longitude,
            visited_poi_ids=[],
            generated_music_ids=[],
            route_history=[route.id],
            total_distance=0.0
        )
        
        db.session.add(session)
        db.session.commit()
        
        return session
    
    def update_session_location(
        self,
        session_id: str,
        location: Location
    ) -> None:
        """Update session with current location.
        
        Args:
            session_id: Session ID
            location: Current location
        """
        session = WalkingSession.query.get(session_id)
        if not session:
            raise ValueError(f"Session {session_id} not found")
        
        if session.status != 'active':
            raise ValueError(f"Cannot update location for session with status {session.status}")
        
        # Calculate distance from previous location if available
        if session.current_latitude and session.current_longitude:
            from app.services.poi_detector_service import POIDetectorService
            detector = POIDetectorService()
            
            # Create Location objects for distance calculation
            from app.models.location import Location as LocationModel
            prev_loc = LocationModel(
                latitude=session.current_latitude,
                longitude=session.current_longitude,
                accuracy=1.0
            )
            curr_loc = LocationModel(
                latitude=location.latitude,
                longitude=location.longitude,
                accuracy=location.accuracy
            )
            
            distance = detector.calculate_distance(prev_loc, curr_loc)
            session.total_distance += distance
        
        # Update current location
        session.current_latitude = location.latitude
        session.current_longitude = location.longitude
        
        db.session.commit()
    
    def end_session(
        self,
        session_id: str
    ) -> Dict:
        """End session and return summary.
        
        Args:
            session_id: Session ID
            
        Returns:
            Session summary
        """
        session = WalkingSession.query.get(session_id)
        if not session:
            raise ValueError(f"Session {session_id} not found")
        
        # Update session status
        session.status = 'completed'
        session.end_time = datetime.utcnow()
        
        db.session.commit()
        
        # Calculate duration
        duration_seconds = 0
        if session.start_time and session.end_time:
            duration_seconds = (session.end_time - session.start_time).total_seconds()
        
        # Return summary
        return {
            'session_id': session.id,
            'user_id': session.user_id,
            'start_time': session.start_time.isoformat() if session.start_time else None,
            'end_time': session.end_time.isoformat() if session.end_time else None,
            'duration_seconds': duration_seconds,
            'total_distance': session.total_distance,
            'visited_poi_ids': session.visited_poi_ids,
            'generated_music_ids': session.generated_music_ids,
            'route_history': session.route_history,
            'status': session.status
        }
    
    def restart_session(
        self,
        session_id: str,
        new_route: Route
    ) -> WalkingSession:
        """Restart session with new route.
        
        Args:
            session_id: Session ID
            new_route: New route
            
        Returns:
            Updated session
        """
        session = WalkingSession.query.get(session_id)
        if not session:
            raise ValueError(f"Session {session_id} not found")
        
        # Update session with new route
        session.route_id = new_route.id
        
        # Add new route to history
        if session.route_history is None:
            session.route_history = []
        session.route_history.append(new_route.id)
        
        # Keep session active
        session.status = 'active'
        
        db.session.commit()
        
        return session
